package com.dengdai.applibrary.https;

import android.net.Uri;
import android.os.Build;

import com.dengdai.applibrary.interfaces.HttpInterface;
import com.dengdai.applibrary.json.Jackson;
import com.dengdai.applibrary.utils.LogUtils;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.nio.charset.Charset;
import java.util.HashMap;
import java.util.Map;
import java.util.Vector;

/**
 * @说明 网络请求
 * @作者 LY
 * @时间 16/5/9 16:19
 * @邮箱 2743569843@qq.com
 * @版权 Copyright(c) 2016 LY-版权所有
 * @备注
 */
public class HttpHelper implements HttpInterface {

    private static HttpHelper mInstance;// 自身实例

    /**
     * 获取对象实例化
     *
     * @return
     */
    public synchronized static HttpHelper getInstance() {
        if (mInstance == null) {
            mInstance = new HttpHelper();
        }
        return mInstance;
    }

    @Override
    public String sendPost(String url, Map<String, Object> params, Map<String, Object> headParameters) throws Exception {
        return send(url, HttpMethods.POST_METHODS, params, headParameters);
    }

    @Override
    public String sendGet(String url, Map<String, Object> params, Map<String, Object> headParameters) throws Exception {
        return send(url, HttpMethods.GET_METHODS, params, headParameters);
    }

    @Override
    public String sendJson(String url, Map<String, Object> params, Map<String, Object> headParameters) throws Exception {
        return send(url, HttpMethods.JSON_METHODS, params, headParameters);
    }

    @Override
    public String sendDelete(String url, Map<String, Object> params, Map<String, Object> headParameters) throws Exception {
        return send(url, HttpMethods.DELETE_METHODS, params, headParameters);
    }


    @Override
    public String sendPut(String url, Map<String, Object> params, Map<String, Object> headParameters) throws Exception {
        return send(url, HttpMethods.PUT_METHODS, params, headParameters);
    }

    @Override
    public String send(String urlStr, String method, Map<String, Object> params, Map<String, Object> headParameters) throws Exception {
        HttpURLConnection urlConnection = null;
        HttpResponse httpResponser = null;
        String responser = null;

        if (method.equals(HttpMethods.GET_METHODS) && params != null) {
            StringBuffer param = new StringBuffer();
            int i = 0;
            for (String key : params.keySet()) {
                if (i == 0)
                    param.append("?");
                else
                    param.append("&");
                param.append(key).append("=").append(Uri.encode(String.valueOf(params.get(key)), "utf-8"));
                i++;
            }
            urlStr += param;
        }
        URL url = new URL(urlStr);
        urlConnection = (HttpURLConnection) url.openConnection();
        urlConnection.setRequestMethod(method.equals(HttpMethods.JSON_METHODS)?HttpMethods.POST_METHODS:method);
        if (Integer.parseInt(Build.VERSION.SDK) < 14) {
            urlConnection.setDoOutput(true);
        }
        urlConnection.setDoInput(true);
        urlConnection.setUseCaches(false);
        urlConnection.setConnectTimeout(6000);
        if (headParameters == null) {
            headParameters = new HashMap<String, Object>();
        }
        if (method.equals(HttpMethods.JSON_METHODS)) {
            headParameters.put("Content-Type", "application/json");
            headParameters.put("Accept", "application/json");
        }
        for (String key : headParameters.keySet()) {
            urlConnection.addRequestProperty(key, String.valueOf(headParameters.get(key)));
        }
        if (method.equals(HttpMethods.POST_METHODS) && params != null) {
            StringBuffer param = new StringBuffer();
            for (String key : params.keySet()) {
                param.append(key).append("=").append(URLEncoder.encode(String.valueOf(params.get(key)), "utf-8"));
                param.append("&");
            }
            urlConnection.getOutputStream().write(param.toString().getBytes());
            urlConnection.getOutputStream().flush();
            urlConnection.getOutputStream().close();
        } else if (method.equals(HttpMethods.JSON_METHODS) && params != null) {
            urlConnection.getOutputStream().write(Jackson.getJSONObject(params).toString().getBytes());
            urlConnection.getOutputStream().flush();
            urlConnection.getOutputStream().close();
        }
        httpResponser = makeContent(urlStr, urlConnection);
        if (httpResponser != null) {
            responser = httpResponser.getContent() == null ? null : httpResponser.getContent().replaceAll("\r\n", "");
        }
        return responser;
    }

    @Override
    public HttpResponse makeContent(String urlString, HttpURLConnection urlConnection) {
        HttpResponse httpResponser = null;
        try {
            httpResponser = new HttpResponse();
            InputStream in = urlConnection.getInputStream();
            BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(in));
            httpResponser.contentCollection = new Vector<String>();
            StringBuffer temp = new StringBuffer();
            String line = bufferedReader.readLine();
            while (line != null) {
                httpResponser.contentCollection.add(line);
                temp.append(line).append("\r\n");
                line = bufferedReader.readLine();
            }
            bufferedReader.close();
            String ecod = urlConnection.getContentEncoding();
            if (ecod == null)
                ecod = Charset.defaultCharset().name();
            httpResponser.urlString = urlString;
            httpResponser.cookie = urlConnection.getHeaderField("Set-Cookie");
            httpResponser.defaultPort = urlConnection.getURL().getDefaultPort();
            httpResponser.file = urlConnection.getURL().getFile();
            httpResponser.host = urlConnection.getURL().getHost();
            httpResponser.path = urlConnection.getURL().getPath();
            httpResponser.port = urlConnection.getURL().getPort();
            httpResponser.protocol = urlConnection.getURL().getProtocol();
            httpResponser.query = urlConnection.getURL().getQuery();
            httpResponser.ref = urlConnection.getURL().getRef();
            httpResponser.userInfo = urlConnection.getURL().getUserInfo();
            httpResponser.content = new String(temp.toString().getBytes(), ecod);
            httpResponser.contentEncoding = ecod;
            httpResponser.code = urlConnection.getResponseCode();
            httpResponser.message = urlConnection.getResponseMessage();
            httpResponser.contentType = urlConnection.getContentType();
            httpResponser.method = urlConnection.getRequestMethod();
            httpResponser.connectTimeout = urlConnection.getConnectTimeout();
            httpResponser.readTimeout = urlConnection.getReadTimeout();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            if (urlConnection != null)
                urlConnection.disconnect();
        }
        return httpResponser;
    }
}
